﻿module StochasticSimulation.GillespieFirstAlgorithm

open System
open StochasticSimulation.ChemicalReaction.ChemicalReaction
open StochasticSimulation.ChemicalReaction.ChemicalSpecies
open Microsoft.FSharp.Collections
     
let executeNextReaction (reactions:seq<Reaction>) (t:float) (rnd:Random) (system:seq<SpeciesCount>)=
    let (firstReaction,timestep) = 
        reactions 
            |> Seq.map ( fun r -> (r, log(1.0/ rnd.NextDouble()) / r.Propensity system) )            
            |> Seq.minBy snd
                    
    { tau =(t + timestep) ; UpdatedSystem =Seq.toList( firstReaction.React(system) ) }